package com.doublethread.easymart.modules.user.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.doublethread.easymart.common.exception.AddressException;
import com.doublethread.easymart.modules.user.dto.AddressDTO;
import com.doublethread.easymart.modules.user.entity.UserAddress;
import com.doublethread.easymart.modules.user.mapper.UserAddressMapper;
import com.doublethread.easymart.modules.user.service.AddressService;
import com.doublethread.easymart.modules.user.vo.UserAddressVO;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.List;

/**
 * 地址服务实现类
 * 专门处理用户收货地址相关业务逻辑
 */
@Slf4j
@Service
public class AddressServiceImpl extends ServiceImpl<UserAddressMapper, UserAddress> implements AddressService {

    @Override
    public List<UserAddressVO> getUserAddressList(Long userId) {
        log.info("获取用户地址列表: userId={}", userId);

        List<UserAddress> addressList = this.list(new LambdaQueryWrapper<UserAddress>()
                .eq(UserAddress::getUserId, userId)
                .eq(UserAddress::getIsDeleted, 0)
                .orderByDesc(UserAddress::getIsDefault)
                .orderByDesc(UserAddress::getCreateTime));

        List<UserAddressVO> result = addressList.stream()
                .map(this::convertToUserAddressVO)
                .toList();

        log.info("获取用户地址列表成功: userId={}, 地址数量={}", userId, result.size());
        return result;
    }

    @Override
    public UserAddressVO getAddressById(Long userId, Long addressId) {
        log.info("获取地址详情: userId={}, addressId={}", userId, addressId);
        // 检查地址归属权限
        UserAddress address = checkAddressOwnership(userId, addressId);
        UserAddressVO result = convertToUserAddressVO(address);

        log.info("获取地址详情成功: userId={}, addressId={}", userId, addressId);
        return result;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public UserAddressVO createAddress(Long userId, AddressDTO addressDTO) {
        log.info("创建地址: userId={}, receiverName={}", userId, addressDTO.getReceiverName());

        // 检查地址数量限制
        long currentCount = checkAddressLimit(userId);
        if (currentCount >= 20) {
            AddressException.addressLimitExceeded();
        }

        // 如果设置为默认地址，先取消其他默认地址
        if (addressDTO.getIsDefault() != null && addressDTO.getIsDefault()) {
            clearDefaultAddress(userId);
        }

        // 创建新地址
        UserAddress address = new UserAddress();
        address.setUserId(userId);
        address.setReceiverName(addressDTO.getReceiverName());
        address.setReceiverPhone(addressDTO.getReceiverPhone());
        address.setProvince(addressDTO.getProvince());
        address.setCity(addressDTO.getCity());
        address.setDistrict(addressDTO.getDistrict());
        address.setDetailAddress(addressDTO.getDetailAddress());
        address.setPostalCode(addressDTO.getPostalCode());
        address.setIsDefault(addressDTO.getIsDefault() != null && addressDTO.getIsDefault() ? 1 : 0);
        address.setIsDeleted(0);

        this.save(address);

        UserAddressVO result = convertToUserAddressVO(address);
        log.info("创建地址成功: userId={}, addressId={}", userId, result.getId());
        return result;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void updateAddress(Long userId, Long addressId, AddressDTO addressDTO) {
        log.info("更新地址: userId={}, addressId={}, receiverName={}",
                userId, addressId, addressDTO.getReceiverName());

        // 检查地址归属权限
        checkAddressOwnership(userId, addressId);

        // 如果设置为默认地址，先取消其他默认地址
        if (addressDTO.getIsDefault() != null && addressDTO.getIsDefault()) {
            clearDefaultAddress(userId, addressId);
        }

        // 更新地址信息
        UserAddress updateAddress = new UserAddress();
        updateAddress.setId(addressId);
        updateAddress.setReceiverName(addressDTO.getReceiverName());
        updateAddress.setReceiverPhone(addressDTO.getReceiverPhone());
        updateAddress.setProvince(addressDTO.getProvince());
        updateAddress.setCity(addressDTO.getCity());
        updateAddress.setDistrict(addressDTO.getDistrict());
        updateAddress.setDetailAddress(addressDTO.getDetailAddress());
        updateAddress.setPostalCode(addressDTO.getPostalCode());
        updateAddress.setIsDefault(addressDTO.getIsDefault() != null && addressDTO.getIsDefault() ? 1 : 0);

        this.updateById(updateAddress);

        log.info("更新地址成功: userId={}, addressId={}", userId, addressId);
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void deleteAddress(Long userId, Long addressId) {
        log.info("删除地址: userId={}, addressId={}", userId, addressId);

        // 检查地址归属权限
        checkAddressOwnership(userId, addressId);

        // 软删除地址
        UserAddress updateAddress = new UserAddress();
        updateAddress.setId(addressId);
        updateAddress.setIsDeleted(1);

        this.updateById(updateAddress);

        log.info("删除地址成功: userId={}, addressId={}", userId, addressId);
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void setDefaultAddress(Long userId, Long addressId) {
        log.info("设置默认地址: userId={}, addressId={}", userId, addressId);

        // 检查地址归属权限
        checkAddressOwnership(userId, addressId);

        // 先取消其他默认地址
        clearDefaultAddress(userId);

        // 设置当前地址为默认
        UserAddress updateAddress = new UserAddress();
        updateAddress.setId(addressId);
        updateAddress.setIsDefault(1);

        this.updateById(updateAddress);

        log.info("设置默认地址成功: userId={}, addressId={}", userId, addressId);
    }

    @Override
    public UserAddressVO getDefaultAddress(Long userId) {
        log.info("获取默认地址: userId={}", userId);

        UserAddress address = this.getOne(new LambdaQueryWrapper<UserAddress>()
                .eq(UserAddress::getUserId, userId)
                .eq(UserAddress::getIsDefault, 1)
                .eq(UserAddress::getIsDeleted, 0));

        if (address == null) {
            log.info("用户没有默认地址: userId={}", userId);
            return null;
        }

        UserAddressVO result = convertToUserAddressVO(address);
        log.info("获取默认地址成功: userId={}, addressId={}", userId, result.getId());
        return result;
    }

    @Override
    public UserAddress checkAddressOwnership(Long userId, Long addressId) {
        UserAddress address = this.getOne(new LambdaQueryWrapper<UserAddress>()
                .eq(UserAddress::getId, addressId)
                .eq(UserAddress::getUserId, userId)
                .eq(UserAddress::getIsDeleted, 0));

        if (address == null) {
            AddressException.addressNotFound();
        }

        return address;
    }

    @Override
    public long checkAddressLimit(Long userId) {
        return this.count(new LambdaQueryWrapper<UserAddress>()
                .eq(UserAddress::getUserId, userId)
                .eq(UserAddress::getIsDeleted, 0));
    }

    @Override
    public String buildFullAddress(UserAddress address) {
        return address.getProvince() + address.getCity() +
                address.getDistrict() + address.getDetailAddress();
    }

    // ==================== 私有辅助方法 ====================

    /**
     * 取消用户的所有默认地址
     */
    private void clearDefaultAddress(Long userId) {
        clearDefaultAddress(userId, null);
    }

    /**
     * 取消用户的所有默认地址（排除指定地址）
     */
    private void clearDefaultAddress(Long userId, Long excludeAddressId) {
        LambdaUpdateWrapper<UserAddress> updateWrapper = new LambdaUpdateWrapper<UserAddress>()
                .eq(UserAddress::getUserId, userId)
                .eq(UserAddress::getIsDefault, 1)
                .set(UserAddress::getIsDefault, 0);

        if (excludeAddressId != null) {
            updateWrapper.ne(UserAddress::getId, excludeAddressId);
        }

        this.update(null, updateWrapper);
    }

    /**
     * 转换UserAddress实体为UserAddressVO
     */
    private UserAddressVO convertToUserAddressVO(UserAddress address) {
        String fullAddress = buildFullAddress(address);

        return UserAddressVO.builder()
                .id(address.getId())
                .receiverName(address.getReceiverName())
                .receiverPhone(address.getReceiverPhone())
                .province(address.getProvince())
                .city(address.getCity())
                .district(address.getDistrict())
                .detailAddress(address.getDetailAddress())
                .postalCode(address.getPostalCode())
                .isDefault(address.getIsDefault() == 1)
                .fullAddress(fullAddress)
                .createTime(address.getCreateTime())
                .updateTime(address.getUpdateTime())
                .build();
    }
}
